# -*- coding: UTF-8 -*-
import os
import urllib2
import json
import datetime
from home.models import Tag, Image
from home.models import Ontology
from home.models import Annotations
from home.models import Recommendations
from home.models import ImageTag
from home.models import TagType
from accounts.models import User 
from django.db import connection
from xml.dom import minidom
import csv
from multi_thread_annotate import startGetAnnotationsFromAnnotator, startGetAnnotationsFromAnnotatorWithMaxLevel
import traceback
import zipfile


#bio的网址
REST_URL = "http://data.bioontology.org"
API_KEY = "1b466c88-c956-4682-8319-5e01f905b4f4"
DOWNLOAD_DIR = "downloads"
    
class annotate:
    def __init__(self):
        self.annotator_list = []
    #
    def getTagIdAndNameOfImageByAnnotations(self,imageId,theKeyword, username):
        resultList = []
        annotations = Annotations.objects.filter(keyword = theKeyword).values_list("tag_id","keyword")
        
        image_tags = ImageTag.objects.filter(image_id = imageId, author_id=username)
        if len(image_tags) == 0:
            return resultList
        for i in annotations:
            try:
                image_tag = ImageTag.objects.get(image_id = imageId, tag_id = i[0], author_id=username)
                if image_tag.isSelected != 1:
                    tag = Tag.objects.get(id = i[0])
                    tagType = TagType.objects.get(id = tag.tag_type_id)
                    ontology = Ontology.objects.get(id = tag.ontology_id)
                    tmp_dict = {
                                'tagID':i[0], 
                                'tagName' :tag.name,
                                'isSelected' :image_tag.isSelected,
                                'tagType' : tagType.tag_type,
                                'ontologyName' : ontology.name,
                                'ontologyID' : ontology.id
                                }
                    resultList.append(tmp_dict)
            except:
                pass
        return resultList
    
    #通过网络获取json数据，获取到的结果文件格式为json
    def get_json(self,url):
        
        get_json_result = []
        try:
            opener = urllib2.build_opener()
            opener.addheaders = [('Authorization', 'apikey token=' + API_KEY)]
            r = opener.open(url).read()
            get_json_result = json.loads(r)
            #r = opener.open(url).read()
            #f = open('json.txt', 'w')
            #f.write(r)
            #print 'testing...'
            #print opener.open('http://data.bioontology.org/ontologies/TESTONTO/classes/http%3A%2F%2Fwww.owl-ontologies.com%2FOntology1394230494.owl%23truc').read()
            #print 'test over'
        except:
            #print 'get_json error'
            #print traceback.print_exc()
            pass
        
        
        return get_json_result
    
    #keyword即为当前搜索的关键词，ontology_ids为指定要搜索的关键词是属于哪一个ontology
    #Annotatons表中存储的是所有已经搜索过的关键词与结果的tag的对应关系，所以遍历Annotations表就可以
    #判断当前关键词是否被搜索过
    def isKeywordSearched(self,currentKeyword,ontology_ids):
        resultList = dict()
        olist = []
        o = Annotations.objects.filter(keyword = currentKeyword).values_list('tag_id')
        if(len(o) > 0):
            for currentTag in o :
                currenttag = Tag.objects.get(id = currentTag[0])
                resultList[currenttag.ontology.virtual_id] = 1
        for t in ontology_ids:
            str = "http://data.bioontology.org/ontologies/" + t
            if not resultList.has_key(str) and t != '':
                olist.append(t)
        return olist

#获取当前Image的，已经给当前Image打过的tag的id和名字，所有的
#tag关系都保存在了image_tags表当中
def getTagIdAndNameOfImage(imageId, username):
    resultList = []
    currUser = User.objects.get(username=username)
    if currUser.isReviewer:
        image_tags = ImageTag.objects.filter(image_id=imageId)
        for i in image_tags:
            tag = Tag.objects.get(id = i.tag_id)
            tagType = TagType.objects.get(id = tag.tag_type_id)
            ontology = Ontology.objects.get(id = tag.ontology_id)
            tmp_dict = {
                        'tagID':i.tag_id,
                        'tagName' :tag.name,
                        'isSelected' :i.isSelected,
                        'tagType' : tagType.tag_type,
                        'ontologyName' : ontology.name,
                        'ontologyID' : ontology.id
                        }
            resultList.append(tmp_dict)
    image_tags = ImageTag.objects.filter(image_id = imageId, author_id=username)
    for i in image_tags:
        tag = Tag.objects.get(id = i.tag_id)
        tagType = TagType.objects.get(id = tag.tag_type_id)
        ontology = Ontology.objects.get(id = tag.ontology_id)
        tmp_dict = {
                    'tagID':i.tag_id,
                    'tagName' :tag.name,
                    'isSelected' :i.isSelected,
                    'tagType' : tagType.tag_type,
                    'ontologyName' : ontology.name,
                    'ontologyID' : ontology.id
                    }
        resultList.append(tmp_dict)
    return resultList

#get selected tags for image
def getTagsForCurrentImage(figureID, username):
    tag_info_list   = list()
    tagList       = ImageTag.objects.filter(image_id=figureID, isSelected=True, author_id=username)
    imageFileName   = Image.objects.get(id=figureID).file_name
    for tagInfos in tagList:
        tagInfo = {
                    'imageFileName': imageFileName,
                    'tagID': tagInfos.tag.id,
                    'tagName': tagInfos.tag.name,
                    'tag_fullID': tagInfos.tag.fullId,
                    'ontologyName':tagInfos.tag.ontology.name,
                    'ontologyVirtualId': tagInfos.tag.ontology.virtual_id,
                    'tagTypeName': tagInfos.tag.tag_type.tag_type,
                    'matchType': tagInfos.matchType,
                    'From': tagInfos.annotationsfrom,
                    'To': tagInfos.annotationsto
        }
        tag_info_list.append(tagInfo)
    return tag_info_list;
#save tags to xml doc
def createTagDoc(tag_info_list):
    doc  = minidom.Document()
    root = doc.createElement("Data")
    doc.appendChild(root)
    for tag_info in tag_info_list:
        node = doc.createElement("Tag")
        for nodeName in tag_info:
            infoNode = doc.createElement("%s" % nodeName)
            data     = doc.createTextNode("%s" % tag_info[nodeName])
            infoNode.appendChild(data)
            node.appendChild(infoNode)
        root.appendChild(node)
    str_xml = doc.toxml("utf-8")
    return str_xml
#save result as xml file
def saveAsXML(figureID,username):
    createDownloadDirectory()

    tag_info_list = getTagsForCurrentImage(figureID, username)
    if len(tag_info_list) == 0:
        return (False, 'NULL')
    str_xml  = createTagDoc(tag_info_list)
    filename = generateFileName(figureID, 'xml')
    f        = open(filename, 'w')
    f.write(str_xml)
    f.close()
    # package file
    packageFileName = generateFileName(figureID, 'xml.zip')
    packageFile = zipfile.ZipFile(packageFileName, mode='w', compression=zipfile.ZIP_STORED)
    packageFile.write(filename, getFileRelPath(filename))
    packageFile.close()
    os.remove(filename)

    return (True, packageFileName)



def oldsaveAsXML(figureID):
    #创建下载目录
    createDownloadDirectory()
    
    
    #这里查询了两次数据库，因为既要查询是否有annotatons，又要查询是否有recommendations
    cursor = connection.cursor()
    cursor1 = connection.cursor()
    cursor.execute("select distinct "+
            "b.file_name as imageFileName,a.id as tagID,a.name as tagName, a.fullId as tag_fullId , d.name as ontologyName, d.virtual_id as ontologyVirtualId, e.tag_type as tagTypeName ,f.matchType as matchtype,"+
            "f.annotationsfrom as annotations_from, f.annotationsto as annotations_to "+
            "from mitagger_tags a ,mitagger_images b, mitagger_image_tags c ,mitagger_ontologies d , mitagger_tag_types e ,mitagger_annotations f "+
            "where a.id = c.tag_id and b.id = c.image_id and f.tag_id = a.id and c.isSelected = 1 and a.ontology_id = d.id and e.id = a.tag_type_id and b.id = %s ;",str(figureID))
    
    result_list = cursor.fetchall()

        
    cursor1.execute("select distinct "+
            "b.file_name as imageFileName,a.id as tagID,a.name as tagName, a.fullId as tag_fullId , d.name as ontologyName, d.virtual_id as ontologyVirtualId, e.tag_type as tagTypeName ,f.matchType as matchtype,"+
            "f.annotationsfrom as annotations_from, f.annotationsto as annotations_to "+
            "from mitagger_tags a ,mitagger_images b, mitagger_image_tags c ,mitagger_ontologies d , mitagger_tag_types e ,mitagger_recommendations f "+
            "where a.id = c.tag_id and b.id = c.image_id and f.tag_id = a.id and c.isSelected = 1 and a.ontology_id = d.id and e.id = a.tag_type_id and b.id = %s ;",str(figureID))
    result_list1 = cursor1.fetchall()
    
    
    if len(result_list) == 0 and len(result_list1) == 0:
        return (False,'NULL')   
    doc = minidom.Document()
    root = doc.createElement("data")
    doc.appendChild(root)
    
    #ATTRIBUTE = {"imageFileName":0,"TagID":1, "TagName":2, "Tag_fullID":3, "OntologyName":4,"TagTypeName":5,"matchType":6,"From":7,"To":8}
    ATTRIBUTE = (
                 ("imageFileName", 0),
                 ("TagID",1), 
                 ("TagName",2), 
                 ("Tag_fullID",3), 
                 ("OntologyName",4),
                 ("ontologyVirtualId",5),
                 ("TagTypeName",6),
                 ("matchType",7),
                 ("From",8),
                 ("To",9)
                 )
    for res in result_list:
        node = doc.createElement("tag")
        for (name,index) in ATTRIBUTE:
            id_node = doc.createElement("%s" % name)
            data = doc.createTextNode("%s" % res[index])
            id_node.appendChild(data)
            node.appendChild(id_node)
        root.appendChild(node)
        
    for res1 in result_list1:
        node = doc.createElement("tag")
        for (name1,index1) in ATTRIBUTE:
            id_node = doc.createElement("%s" % name1)
            data = doc.createTextNode("%s" % res1[index1])
            id_node.appendChild(data)
            node.appendChild(id_node)
        root.appendChild(node)    
    
    str_xml = doc.toxml("utf-8")
    #TODO: Add extension name here
    filename = generateFileName(figureID,'xml')
    
    f = open(filename, 'w')
    f.write(str_xml)
    f.close()
    
    packageFileName = generateFileName(figureID,'xml.zip')
    packageFile = zipfile.ZipFile(packageFileName, mode = 'w', compression=zipfile.ZIP_STORED)
    packageFile.write(filename, getFileRelPath(filename))
    packageFile.close()
    os.remove(filename)
        
    cursor.close()
    cursor1.close()
    #tag complete
    #im= Image.objects.get(id = figureID)
    #im.is_tagged = True
    #im.save()
    
    
    return (True,packageFileName)

def getTagForImages(figureIDs, username):
    tagList = ImageTag.objects.filter(image_id__in=figureIDs, author_id=username, isSelected=True)
    result_list = list()
    for tagObj in tagList:
        tagInfo = {
            'imageFileName': tagObj.image.file_name,
            'tagID': tagObj.tag.id,
            'tagName': tagObj.tag.name,
            'tag_fullID': tagObj.tag.fullId,
            'ontologyName':tagObj.tag.ontology.name,
            'ontologyVirtualId': tagObj.tag.ontology.virtual_id,
            'tagTypeName': tagObj.tag.tag_type.tag_type,
            'matchType': tagObj.matchType,
            'From': tagObj.annotationsfrom,
            'To': tagObj.annotationsto
        }
        result_list.append(tagInfo)
    return result_list


def saveAsXMLs(figureIDs, username):
    createDownloadDirectory()
    #get tags for images
    tag_info_list = getTagForImages(figureIDs, username)

    if len(tag_info_list) == 0:
        return (False, 'NULL')
    #write tag infos to xml file
    str_xml  = createTagDoc(tag_info_list)
    filename = generateFileName(username, 'xml')
    f        = open(filename, 'w')
    f.write(str_xml)
    f.close()
    # package file
    packageFileName = generateFileName(username, 'xml.zip')
    packageFile = zipfile.ZipFile(packageFileName, mode='w', compression=zipfile.ZIP_STORED)
    packageFile.write(filename, getFileRelPath(filename))
    packageFile.close()
    os.remove(filename)

    return (True, packageFileName)


#保存结果文件为xml格式，这里的保存是保存多个image的结果
def oldsaveAsXMLs(figureIDs,username):
    createDownloadDirectory()
    #figureIDList即为要保存的所有图片的id
    figureIDList = ','.join(figureIDs)
    cursor = connection.cursor()
    
    cursor1 = connection.cursor()
    #print figureIDList

    cursor.execute("select distinct "+
            "b.file_name as imageFileName,a.id as tagID,a.name as tagName, a.fullId as tag_fullId , d.name as ontologyName, d.virtual_id as ontologyVirtualId,e.tag_type as tagTypeName ,f.matchType as matchtype,"+
            "f.annotationsfrom as annotations_from, f.annotationsto as annotations_to "+
            "from mitagger_tags a ,mitagger_images b, mitagger_image_tags c ,mitagger_ontologies d , mitagger_tag_types e,mitagger_annotations f "+
            "where a.id = c.tag_id and b.id = c.image_id and f.tag_id = a.id and c.isSelected = 1 and a.ontology_id = d.id and e.id = a.tag_type_id and b.id in ("+figureIDList+") order by imageFileName;")
    
    result_list = cursor.fetchall()

    
    cursor1.execute("select distinct "+
            "b.file_name as imageFileName,a.id as tagID,a.name as tagName, a.fullId as tag_fullId , d.name as ontologyName,d.virtual_id as ontologyVirtualId, e.tag_type as tagTypeName ,f.matchType as matchtype,"+
            "f.annotationsfrom as annotations_from, f.annotationsto as annotations_to "+
            "from mitagger_tags a ,mitagger_images b, mitagger_image_tags c ,mitagger_ontologies d , mitagger_tag_types e,mitagger_recommendations f "+
            "where a.id = c.tag_id and b.id = c.image_id and f.tag_id = a.id and c.isSelected = 1 and a.ontology_id = d.id and e.id = a.tag_type_id and b.id in ("+figureIDList+") order by imageFileName;")
    
    result_list1 = cursor1.fetchall()
    
    
    if len(result_list) == 0 and len(result_list1) == 0:
        return (False,'NULL')   
    
    doc = minidom.Document()
    root = doc.createElement("data")
    doc.appendChild(root)
    
    #ATTRIBUTE = {"imageFileName":0,"TagID":1, "TagName":2, "Tag_fullID":3, "OntologyName":4,"TagTypeName":5,"matchType":6,"From":7,"To":8}
    ATTRIBUTE = (
                 ("imageFileName", 0),
                 ("TagID",1), 
                 ("TagName",2), 
                 ("Tag_fullID",3), 
                 ("OntologyName",4),
                 ("ontologyVirtualId",5),
                 ("TagTypeName",6),
                 ("matchType",7),
                 ("From",8),
                 ("To",9)
                 )
    for res in result_list:
        node = doc.createElement("tag")
        for (name,index) in ATTRIBUTE:
            id_node = doc.createElement("%s" % name)
            data = doc.createTextNode("%s" % res[index])
            id_node.appendChild(data)
            node.appendChild(id_node)
        root.appendChild(node)
        
    for res in result_list1:
        node = doc.createElement("tag")
        for (name,index) in ATTRIBUTE:
            id_node = doc.createElement("%s" % name)
            data = doc.createTextNode("%s" % res[index])
            id_node.appendChild(data)
            node.appendChild(id_node)
        root.appendChild(node)
    str_xml = doc.toxml("utf-8")
    
    #TODO: Add extension name here
    filename = generateFileName(username,'xml')
    
    f = open(filename, 'w')
    f.write(str_xml)
    f.close()
    
    cursor.close()
    cursor1.close()
    #tag complete
    #for currentId in figureIDs:
    #    im= Image.objects.get(id = currentId)
    #    im.is_tagged = True
    #    im.save()

    return (True,filename)


def saveAsCSVs(figureIDs, username):
    createDownloadDirectory()
    tag_info_list = getTagForImages(figureIDs, username)
    if len(tag_info_list) == 0:
        return (False, 'NULL')
    filename = writeResultToCSV(username, tag_info_list)
    return (True, filename)

#保存结果文件为csv格式，这里的保存是保存多个图片的结果
def oldsaveAsCSVs(figureIDs,username):
    createDownloadDirectory()
    #figureIDList即为要保存的所有图片的id
    figureIDList = ','.join(figureIDs)
    cursor = connection.cursor()
    cursor1 = connection.cursor()
    cursor.execute("select distinct "+
            "b.file_name as imageFileName,a.id as tagID,a.name as tagName, a.fullId as tag_fullId , d.name as ontologyName, e.tag_type as tagTypeName ,f.matchType as matchtype,"+
            "f.annotationsfrom as annotations_from, f.annotationsto as annotations_to "+
            "from mitagger_tags a ,mitagger_images b, mitagger_image_tags c ,mitagger_ontologies d , mitagger_tag_types e,mitagger_annotations f "+
            "where a.id = c.tag_id and b.id = c.image_id and f.tag_id = a.id and c.isSelected = 1 and a.ontology_id = d.id and e.id = a.tag_type_id and b.id in ("+figureIDList+") order by imageFileName;")
    result_list = cursor.fetchall()

    cursor1.execute("select distinct "+
            "b.file_name as imageFileName,a.id as tagID,a.name as tagName, a.fullId as tag_fullId , d.name as ontologyName, e.tag_type as tagTypeName ,f.matchType as matchtype,"+
            "f.annotationsfrom as annotations_from, f.annotationsto as annotations_to "+
            "from mitagger_tags a ,mitagger_images b, mitagger_image_tags c ,mitagger_ontologies d , mitagger_tag_types e,mitagger_recommendations f "+
            "where a.id = c.tag_id and b.id = c.image_id and f.tag_id = a.id and c.isSelected = 1 and a.ontology_id = d.id and e.id = a.tag_type_id and b.id in ("+figureIDList+") order by imageFileName;")
    
    result_list1 = cursor1.fetchall()
    if len(result_list) == 0 and len(result_list1) == 0:
        return (False,'NULL')   
    filename = generateFileName(username,'csv')
    csv_writer = csv.writer(open(filename, "wb"), delimiter=',')  
    csv_writer.writerow([i[0] for i in cursor.description]) # write headers  
    csv_writer.writerows(cursor)
    csv_writer.writerows(cursor1)
    cursor.close()
    del csv_writer # this will close the CSV file
        
    #tag complete
    #for currentId in figureIDs:
    #    im= Image.objects.get(id = currentId)
    #    im.is_tagged = True
    #    im.save()
    return (True,filename)

def writeResultToCSV(identifier, tag_info_list):
    filename = generateFileName(identifier, 'csv')
    csv_writer = csv.writer(open(filename, 'wb'), delimiter=',')
    rows_list = list()
    rows_list.append([i for i in tag_info_list[0]])
    for tag_info in tag_info_list:
        row = list()
        for key in tag_info:
            row.append(tag_info[key])
        rows_list.append(row)
    csv_writer.writerows(rows_list)
    del csv_writer
    return filename
def saveAsCSV(figureID, username):
    createDownloadDirectory()
    tag_info_list = getTagsForCurrentImage(figureID, username)
    if len(tag_info_list) == 0:
        return (False, 'NULL')
    filename = writeResultToCSV(figureID, tag_info_list)
    return (True, filename)

#保存结果文件为CSV格式
def osaveAsCSV(figureID):
    createDownloadDirectory()
    
    cursor = connection.cursor()  
    cursor1 = connection.cursor()
    #select a.name as tagName, a.fullId as tag_fullId , d.name as ontologyName, e.tag_type as tagTypeName from mitagger_tags a ,mitagger_images b, mitagger_image_tags c ,mitagger_ontologies d , mitagger_tag_types e where a.id = c.tag_id and b.id = c.image_id and a.ontology_id = d.id and e.id = a.tag_type_id;
    #select * from mitagger_tags a ,mitagger_images b, mitagger_image_tags c ,mitagger_ontologies d , mitagger_tag_types e where a.id = c.tag_id and b.id = c.image_id and a.ontology_id = d.id and e.id = a.tag_type_id;
    cursor.execute('''
        select distinct
            b.file_name as imageFileName, a.id as tagID, a.name as tagName, a.fullId as tag_fullId, 
            d.name as ontologyName, d.virtual_id as ontologyVirtualId, e.tag_type as tagTypeName,
            f.matchType as matchtype, f.annotationsfrom as annotations_from, f.annotationsto as annotations_to 
        from 
            mitagger_tags a, mitagger_images b, mitagger_image_tags c, mitagger_ontologies d, 
            mitagger_tag_types e ,mitagger_annotations f
        where 
            a.id = c.tag_id and b.id = c.image_id and f.tag_id = a.id and c.isSelected = 1 and
            a.ontology_id = d.id and e.id = a.tag_type_id and b.id = %s;''',str(figureID))
    
    result_list = cursor.fetchall()
 
    filename = generateFileName(figureID,'csv')
    csv_writer = csv.writer(open(filename, "wb"), delimiter=',')  
    csv_writer.writerow([i[0] for i in cursor.description]) # write headers  
    csv_writer.writerows(cursor)
    
    
    cursor1.execute("select distinct "+
            "b.file_name as imageFileName,a.id as tagID,a.name as tagName, a.fullId as tag_fullId , d.name as ontologyName, d.virtual_id as ontologyVirtualId, e.tag_type as tagTypeName ,f.matchType as matchtype,"+
            "f.annotationsfrom as annotations_from, f.annotationsto as annotations_to "+
            "from mitagger_tags a ,mitagger_images b, mitagger_image_tags c ,mitagger_ontologies d , mitagger_tag_types e ,mitagger_recommendations f "+
            "where a.id = c.tag_id and b.id = c.image_id and f.tag_id = a.id and c.isSelected = 1 and a.ontology_id = d.id and e.id = a.tag_type_id and b.id = %s;",str(figureID))
    result_list1 = cursor1.fetchall()
    csv_writer.writerows(cursor1)
    
    if len(result_list) == 0 and len(result_list1) == 0:
        return (False,'NULL')   
    
    cursor.close()
    cursor1.close()
    del csv_writer # this will close the CSV file
        
    #tag complete
    #im= Image.objects.get(id = figureID)
    #im.is_tagged = True
    #im.save()
    return (True,filename)

def saveAll(username):
    taggedImagesByUser = ImageTag.objects.filter(author_id=username).values_list('image_id',flat=True)
    if len(taggedImagesByUser) == 0:
        return False, 'NULL'
    isXmlFileCreatedSuccessful, xmlFileName = saveAsXMLs(taggedImagesByUser, username)
    isCsvFileCreatedSuccessful, csvFileName = saveAsCSVs(taggedImagesByUser, username)
    if isXmlFileCreatedSuccessful and isCsvFileCreatedSuccessful:
        packageFileName = generateFileName(username,'zip')
        
        packageFile = zipfile.ZipFile(packageFileName, mode = 'w', compression=zipfile.ZIP_STORED)
    
        packageFile.write(xmlFileName, getFileRelPath(xmlFileName))
        packageFile.write(csvFileName, getFileRelPath(csvFileName))
        packageFile.close()
        
        os.remove(xmlFileName)
        os.remove(csvFileName)
    
        return (True,packageFileName)
    else:
        return False, 'NULL'
#保存全部结果，即保存当前用户打过的所有图片的所有结果
def oldsaveAll(username):
    
    packageFileNameList = []
    
    taggedImagesByUserList= Image.objects.filter(tag_maker_id = username).values_list('id')
    
    if len(taggedImagesByUserList) == 0:
        return 
    
    for i in taggedImagesByUserList:
        packageFileNameList.append(str(i[0]))
    
    
    isXmlFileCreatedSuccessful,xmlFileName = saveAsXMLs(packageFileNameList,username)
    isCsvFileCreatedSuccessful,csvFileName = saveAsCSVs(packageFileNameList,username)
    if isXmlFileCreatedSuccessful and isCsvFileCreatedSuccessful:
        packageFileName = generateFileName(username,'zip')
        
        packageFile = zipfile.ZipFile(packageFileName, mode = 'w', compression=zipfile.ZIP_STORED)
    
        packageFile.write(xmlFileName, getFileRelPath(xmlFileName))
        packageFile.write(csvFileName, getFileRelPath(csvFileName))
        packageFile.close()
        
        os.remove(xmlFileName)
        os.remove(csvFileName)
    
        return (True,packageFileName)
    else:
        return (False,"NULL")
#保存当前图片的结果信息，即保存成csv和xml两种文件格式
def saveBoth(figureID, username):
    createDownloadDirectory()
    
    isCsvFileCreatedSuccessful,csvFileName = saveAsCSV(figureID, username)
    isXmlFileCreatedSuccessful,xmlFileName = saveAsXML(figureID, username)

    if isCsvFileCreatedSuccessful and isXmlFileCreatedSuccessful:
        #print "in"
        packageFileName = generateFileName(figureID,'zip')
        
        packageFile = zipfile.ZipFile(packageFileName, mode = 'w', compression=zipfile.ZIP_STORED)
        packageFile.write(csvFileName, getFileRelPath(csvFileName))
        packageFile.write(xmlFileName, getFileRelPath(xmlFileName))
        
        packageFile.close()
        
        os.remove(csvFileName)
        os.remove(xmlFileName)
            
        #tag complete
        #im= Image.objects.get(id = figureID)
        #im.is_tagged = True
        #im.is_tagging = False
        #im.save()
        return (True,packageFileName)
    else:
        return (False,"NULL")

def createDownloadDirectory():
    if not os.path.exists(DOWNLOAD_DIR):
        os.mkdir(DOWNLOAD_DIR)
        
def getFileRelPath(fileName):
    dirName = os.path.dirname(fileName)
    relPath = os.path.relpath(fileName, dirName)
    
    return relPath

def generateFileName(figureID, extension):
    now = datetime.datetime.now()
    fileNameFormat = '%(year)i-%(month)i-%(day)i-%(hour)i-%(minute)i-%(second)i-figureID=%(figureID)s.%(extension)s'
    fileNameValue = {
                     'year' : now.year,
                     'month' : now.month,
                     'day' : now.day,
                     'hour' : now.hour,
                     'minute' : now.minute,
                     'second' : now.second,
                     'figureID' : figureID,
                     'extension' : extension
                     }
    baseURL = DOWNLOAD_DIR + '/'
    return baseURL + (fileNameFormat % fileNameValue)
    
#删除一条tag，不是删除tag的数据，而是删除当前图片与该tag的关系
def removeATag(figureID, tagID, username):
    #tag = Tag.objects.get(id = tagID)
    imageTag = ImageTag.objects.get(image_id = figureID,tag_id = tagID, author_id = username)
    imageTag.delete()
    #tag.delete()
    return True

#给图片打上一个ImageType
def tagAImageType(figureID,imageTypeName,username):
    o = Ontology.objects.get(name = "Image Type")
    t,isT = Tag.objects.get_or_create(name = imageTypeName,tag_type_id=3,fullId="null",ontology_id = o.id)
    i,isI = ImageTag.objects.get_or_create(image_id = figureID,tag_id = t.id,author_id=username,isSelected = 1)
    
    curentImage= Image.objects.get(id = figureID)
    curentImage.tag_maker_id =username
    curentImage.save()
    
    result = {
              'isSuccessful': True,
              'tagID': t.id
              }
    
    return result

#打Tag，即修改ImageTag关系表，将tag与image的对应关系加载到表中，即意味着给当前图片打上了一个tag
def setTagSelected(figureID,tagID,isSelected,username):
    i,isC = ImageTag.objects.get_or_create(image_id = figureID, tag_id = tagID, author_id=username)
    i.isSelected = isSelected
    i.save()
    
    curentImage= Image.objects.get(id = figureID)
    curentImage.tag_maker_id =username
    curentImage.save()
    
    return True 


def saveAnnotateTagFromDatabaseToImageTag(figureID,theKeyword,annotations, username):
    print len(annotations)
    for annotateIndex in range(len(annotations)):
        try:
            currentAnnotatedClass = annotations[annotateIndex]["annotatedClass"]
            currentAnnotations = annotations[annotateIndex]["annotations"]
            currentOntology = Ontology.objects.get(virtual_id = currentAnnotatedClass["links"]["ontology"])
            
            currentTag = Tag.objects.get(fullId = currentAnnotatedClass["@id"],ontology_id = currentOntology.id)
            
            if currentTag.tag_type_id == 4:
                currentTag.tag_type_id = '1'
                currentTag.save()
            try:
                imageTag,isImageTagCreated = ImageTag.objects.get_or_create(image_id = figureID,tag_id=currentTag.id,
                                                                            author_id=username, isSelected = 0,
                                                                            annotationsfrom=currentAnnotations[0]["from"],
                                                                            annotationsto=currentAnnotations[0]["to"],
                                                                            matchType=currentAnnotations[0]["matchType"])
            except:
                print 'error1'
                pass

            Annotations.objects.get_or_create(tag_id =currentTag.id,keyword = theKeyword ,
                                              annotationsfrom=currentAnnotations[0]["from"],
                                              annotationsto=currentAnnotations[0]["to"],
                                              matchType=currentAnnotations[0]["matchType"])
        except Tag.DoesNotExist:
            print currentTag
            print 'error2'
            #TODO: the unsaved tag 
#             baseURL = currentAnnotatedClass["links"]["ontology"] + "/classes/"
#             tagURL = baseURL + urllib2.quote(currentAnnotatedClass["@id"])
            
            pass
            
    return True


#
def finalize(figureID):
    
    currentImage = Image.objects.get(id = figureID)
    currentImage.is_tagged = "1"
    currentImage.save()
    
    return True

#
def oldsaveRecommendTagFromAnnotations(figureID,theKeyword, username):
    
    currentAnnotations = Annotations.objects.filter(keyword = theKeyword).values_list("tag_id")
    
    for currentTagID in currentAnnotations:
        #print type(currentTagID[0])
        #print currentTagID[0]
        currentImageTag = ImageTag.objects.filter(image_id = figureID,tag_id = currentTagID[0], author_id=username)
        
        currentTag = ImageTag.objects.filter(tag_id = currentTagID[0])
        
        if len(currentImageTag) == 0:

            currentImageTag= ImageTag(image_id = figureID,tag_id = currentTagID[0],author_id = username, isSelected = 0)
            currentImageTag.save()

def saveRecommendTagFromAnnotations(figureID, theKeyword, username):
    annotation_list = Annotations.objects.filter(keyword=theKeyword)

    for annotation in annotation_list:
        if len(ImageTag.objects.filter(image_id=figureID, tag=annotation.tag, author_id=username)) == 0:
            newImageTag = ImageTag(image_id=figureID, tag=annotation.tag, author_id=username, isSelected=0, annotationsfrom=annotaion.annotationsfrom, annotationsto=annotation.annotationsto, matchType=annotation.matchType)
            newImageTag.save()
            
#调用函数，keyword为要查询的关键字，figureID为当前图片的id，ontology_ids为进行搜索操作时，规定好了的ontology范围
def getTagsByGO(keyword,figureID,ontology_ids, username):
    annotateInstance = annotate()
    ontologiesToSearch = annotateInstance.isKeywordSearched(keyword,ontology_ids.split(','))
    #print ontologiesToSearch
    #判断，ontologiesToSearch的意思是还需要进行搜索的ontology，即数据库中不存在的数据
    #如果需要搜索的数据为0，那么就不需要进行网络查询，直接从recommendation表中查询结果数据
    if len(ontologiesToSearch) == 0:
        #print "if"
        saveRecommendTagFromAnnotations(figureID,keyword, username)
    #否则
    else:
        #print "else"
        #进行查询，拿到结果文件
        annotate_result = startGetAnnotationsFromAnnotator(keyword,','.join(ontologiesToSearch))
        #print type(annotate_result)
        #通过对结果文件的解析，将结果存储到数据库，并将对应关系存储到ImageTag表中
        saveAnnotateTagFromDatabaseToImageTag(figureID,keyword,annotate_result, username)
        
    return annotateInstance.getTagIdAndNameOfImageByAnnotations(figureID,keyword, username)

def get_json(url):
    try:
        print 'Success'
        opener = urllib2.build_opener()
        opener.addheaders = [('Authorization', 'apikey token=' + API_KEY)]
        return json.loads(opener.open(url).read()), True
    except:
        print 'Fail'
        return {}, False

def isKeywordCached(keyword, ontology_ids):
    anno_list = Annotations.objects.filter(keyword=keyword)
    return len(anno_list) != 0

def saveCacheResult(keyword, figureID, username):
    # get annotation cache
    anno_list = Annotations.objects.filter(keyword=keyword)
    result_list = []
    for anno_obj in anno_list:
        try:
            ImageTag.objects.get(image_id=figureID, tag=anno_obj.tag, isSelected=False, author_id=username)
        except:
            new_it_obj = ImageTag(image_id=figureID, tag=anno_obj.tag, isSelected=False, author_id=username)
            new_it_obj.save()
        tmp_dict = {
            'tagID':anno_obj.tag.id, 
            'tagName' :anno_obj.tag.name,
            'isSelected' :False,
            'tagType' : anno_obj.tag.tag_type.tag_type,
            'ontologyName' : anno_obj.tag.ontology.name,
            'ontologyID' : anno_obj.tag.ontology.id
        }
        result_list.append(tmp_dict)
    return result_list

def get_new_tag(url):
    tag_json, isSuccessful = get_json(url)
    if not isKeywordCached:
        return None
    tag_name = tag_json['prefLabel']
    id_pos = tag_json['@id'].rfind('/') + 1
    tag_id = tag_json['@id'][id_pos:]
    tag_type = 2
    fullId = tag_json['@id']
    ontology = tag_json['links']['ontology']
    try:
        ontology_obj = Ontology.objects.get(virtual_id=ontology)
    except:
        return None
    try:
        new_tag_obj = Tag(id=tag_id, name=tag_name, fullId=fullId, ontology=ontology_obj)
        new_tag_obj.save()
        return new_tag_obj
    except:
        return None


def cacheSearchResult(anno_list, keyword, figureID, username):
    res_list = []
    for index in range(len(anno_list)):
        curr_anno = anno_list[index]['annotatedClass']
        curr_anno_info = anno_list[index]['annotations']
        try:
            tag_obj = Tag.objects.get(fullId=curr_anno['@id'])
            tmp_dict = {
                'tagID':tag_obj.id,
                'tagName':tag_obj.name,
                'isSelected': False,
                'tagType': tag_obj.tag_type.tag_type,
                'ontologyName': tag_obj.ontology.name,
                'ontologyID': tag_obj.ontology.id
            }
            try:
                new_im = ImageTag(image_id=figureID, tag=tag_obj, author_id=username,
                    annotationsfrom=curr_anno_info[0]['from'],
                    annotationsto=curr_anno_info[0]['to'],
                    matchType=curr_anno_info[0]['matchType'])
                new_im.save()
                res_list.append(tmp_dict)
            except:
                pass
            try:
                Annotations.objects.get(tag_id=tag_obj.id, keyword=keyword,
                    annotationsfrom=curr_anno_info[0]['from'],
                    annotationsto=curr_anno_info[0]['to'],
                    matchType=curr_anno_info[0]['matchType'])
            except:
                new_anno_obj = Annotations(tag_id=tag_obj.id, keyword=keyword,
                        annotationsfrom=curr_anno_info[0]['from'],
                        annotationsto=curr_anno_info[0]['to'],
                        matchType=curr_anno_info[0]['matchType'])
                new_anno_obj.save()
        except:
            print 'getting tag'
            #save new tag
            try:
                id_pos = curr_anno['@id'].rfind('/') + 1
                tagUrl = curr_anno["links"]["ontology"] + "/classes/" + curr_anno['@id']['id_pos':]
                print tagUrl
                new_tag = get_new_tag(tagUrl)
                if new_tag != None:
                    tmp_dict = {
                        'tagID':new_tag.id,
                        'tagName':new_tag.name,
                        'isSelected': False,
                        'tagType': new_tag.tag_type.tag_type,
                        'ontologyName': new_tag.ontology.name,
                        'ontologyID': new_tag.ontology.id
                    }
                try:
                    new_im = ImageTag(image_id=figureID, tag=new_tag, author_id=username,
                        annotationsfrom=curr_anno_info[0]['from'],
                        annotationsto=curr_anno_info[0]['to'],
                        matchType=curr_anno_info[0]['matchType'])
                    new_im.save()
                    res_list.append(tmp_dict)
                except:
                    pass
            except:
                pass
    return res_list

def getTagsByKeyword(keyword, figureID, ontology_ids, maxLevel, username):
    #search in cache, if result not in cache, search with bioontology
    res = []
    if isKeywordCached(keyword, ontology_ids):
        pass
        # get tags from database & save
        res = saveCacheResult(keyword, figureID, username)
    else:
        pass
        # search & cache result
        annotation_list, isSuccessful = getAnnotationWithMaxLevel(keyword, ontology_ids, maxLevel)
        if not isSuccessful:
            pass
        else:
            res = cacheSearchResult(annotation_list, keyword, figureID, username)
    return res
    


#调用函数，keyword为要查询的关键字，figureID为当前图片的id，ontology_ids为进行搜索操作时，规定好了的ontology范围，maxLevel是搜索的最大层次
def oldgetTagsByKeyword(keyword,figureID,ontology_ids,maxLevel, username):
    annotateInstance = annotate()
    ontologiesToSearch = annotateInstance.isKeywordSearched(keyword,ontology_ids.split(','))
    #print ontologiesToSearch
    #判断，ontologiesToSearch的意思是还需要进行搜索的ontology，即数据库中不存在的数据
    #如果需要搜索的数据为0，那么就不需要进行网络查询，直接从recommendation表中查询结果数据
    if len(ontologiesToSearch) == 0:
        #print "if"
        saveRecommendTagFromAnnotations(figureID,keyword, username)
    #否则
    else:
        #print "else"
        #进行查询，拿到结果文件
        annotate_result, isSuccessful = getAnnotationWithMaxLevel(keyword,','.join(ontologiesToSearch), maxLevel)
        if not isSuccessful:
            return []
        #print type(annotate_result)
        #通过对结果文件的解析，将结果存储到数据库，并将对应关系存储到ImageTag表中
        saveAnnotateTagFromDatabaseToImageTag(figureID,keyword,annotate_result, username)
        
    return annotateInstance.getTagIdAndNameOfImageByAnnotations(figureID,keyword, username)

def getAnnotationWithMaxLevel(figureLegend,ontology_ids,max_level):
    annotations, isSuccessful = get_json(REST_URL + 
                             "/annotator?max_level=1&text=" + 
                             urllib2.quote(figureLegend) +
                             "&ontologies=" +
                             ontology_ids
                             )
    #annotations = ontologies.search(figureLegend, ontology_ids)
    return annotations, isSuccessful

#分配给用户某些image
def assignImage(figureIDStart,figureIDEnd,username):
    images = Image.objects.filter(id = '1')
    for currentImage in images:
        currentImageId = currentImage[0]
        currentImage


    result = {
              'maxID':Image.objects.last().id,
              'minID':Image.objects.first().id
              }
#assignImage(1,2,"areshero")

    
    
#saveAsCSV('950')
